package com.icoolkj.ms.pay.service.impl;

import com.icoolkj.ms.api.pay.dto.MemberRechargeDTO;
import com.icoolkj.ms.api.pay.model.MemberRecharge;
import com.icoolkj.ms.api.pay.model.RechargePackage;
import com.icoolkj.ms.api.pay.vo.RechargeResultVO;
import com.icoolkj.ms.common.core.response.ServerResponseEntity;
import com.icoolkj.ms.pay.constant.PayConstant;
import com.icoolkj.ms.pay.feign.MemberFeignClient;
import com.icoolkj.ms.pay.mapper.MemberRechargeMapper;
import com.icoolkj.ms.pay.mapper.RechargePackageMapper;
import com.icoolkj.ms.api.pay.model.PayOrder;
import com.icoolkj.ms.pay.service.MemberRechargeService;
import com.icoolkj.ms.pay.service.PayService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;

/**
 * 会员充值服务实现类
 *
 * @author icoolkj
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class MemberRechargeServiceImpl implements MemberRechargeService {

    @Qualifier("wechatPayService")
    private final PayService wechatPayService;

    @Qualifier("alipayService")
    private final PayService alipayService;

    private final MemberRechargeMapper memberRechargeMapper;
    
    private final RechargePackageMapper rechargePackageMapper;
    
    private final MemberFeignClient memberFeignClient;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ServerResponseEntity<RechargeResultVO> createRechargeOrder(Long memberId, MemberRechargeDTO rechargeDTO) {
        try {
            // 查询充值套餐
            RechargePackage rechargePackage = rechargePackageMapper.selectById(rechargeDTO.getPackageId());
            if (rechargePackage == null) {
                return ServerResponseEntity.fail("充值套餐不存在");
            }
            
            if (!"1".equals(rechargePackage.getStatus())) {
                return ServerResponseEntity.fail("充值套餐已下架");
            }
            
            // 生成订单号
            String orderNo = generateOrderNo();
            
            // 创建充值记录
            MemberRecharge memberRecharge = new MemberRecharge();
            memberRecharge.setMemberId(memberId);
            memberRecharge.setOrderNo(orderNo);
            memberRecharge.setAmount(rechargePackage.getAmount());
            memberRecharge.setGiftAmount(calculateGiftAmount(rechargePackage.getAmount()));
            memberRecharge.setPayType(rechargeDTO.getPayType());
            memberRecharge.setStatus(PayConstant.OrderStatus.WAIT_PAY);
            memberRecharge.setCreateTime(new Date());
            memberRecharge.setRemark(rechargeDTO.getRemark());
            // 设置创建者（一般为当前登录用户的用户名或ID）
            memberRecharge.setCreateBy(memberId.toString());
            memberRecharge.setUpdateBy(memberId.toString());
            
            // 保存充值记录到数据库
            memberRechargeMapper.insert(memberRecharge);
            
            // 构建返回结果
            RechargeResultVO resultVO = new RechargeResultVO();
            resultVO.setOrderNo(orderNo);
            resultVO.setAmount(rechargePackage.getAmount());
            resultVO.setPayType(rechargeDTO.getPayType());
            
            // 此处不调用支付服务创建支付参数，前端调用getPaymentParams接口获取支付参数
            resultVO.setPayParams(new HashMap<>());
            
            return ServerResponseEntity.success(resultVO);
        } catch (Exception e) {
            log.error("创建充值订单失败", e);
            return ServerResponseEntity.fail("创建充值订单失败: " + e.getMessage());
        }
    }
    
    @Override
    public ServerResponseEntity<Map<String, String>> getPaymentParams(String orderNo, String payType) {
        try {
            // 查询充值订单
            MemberRecharge memberRecharge = memberRechargeMapper.selectByOrderNo(orderNo);
            if (memberRecharge == null) {
                return ServerResponseEntity.fail("充值订单不存在");
            }
            
            if (!PayConstant.OrderStatus.WAIT_PAY.equals(memberRecharge.getStatus())) {
                return ServerResponseEntity.fail("订单状态不正确，无法支付");
            }
            
            // 创建支付订单
            PayOrder payOrder = new PayOrder();
            payOrder.setOrderNo(orderNo);
            payOrder.setAmount(memberRecharge.getAmount());
            payOrder.setSubject("会员充值-" + memberRecharge.getAmount() + "元");
            payOrder.setBody("会员账户充值" + memberRecharge.getAmount() + "元");
            
            // 根据支付类型选择支付服务
            PayService payService = getPayService(payType);
            Map<String, String> payParams = payService.createOrder(payOrder);
            
            return ServerResponseEntity.success(payParams);
        } catch (Exception e) {
            log.error("获取支付参数失败", e);
            return ServerResponseEntity.fail("获取支付参数失败: " + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ServerResponseEntity<Boolean> handlePayNotify(String payType, Map<String, String> params) {
        try {
            // 根据支付类型选择支付服务处理通知
            PayService payService = getPayService(payType);
            boolean result = payService.handlePayNotify(payType, params);
            
            if (result) {
                // 获取订单号
                String orderNo = params.get("out_trade_no");
                String transactionId = params.get("transaction_id");
                
                // 从数据库查询充值记录
                MemberRecharge memberRecharge = memberRechargeMapper.selectByOrderNo(orderNo);
                if (memberRecharge != null) {
                    // 更新充值记录状态
                    memberRecharge.setStatus(PayConstant.OrderStatus.PAY_SUCCESS);
                    memberRecharge.setRechargeTime(new Date());
                    memberRecharge.setTransactionId(transactionId);
                    memberRechargeMapper.updateByOrderNo(memberRecharge);
                    
                    // 查询套餐信息
                    RechargePackage rechargePackage = getRechargePackageByAmount(memberRecharge.getAmount());
                    
                    // 更新会员账户余额
                    updateMemberBalance(memberRecharge.getMemberId(), 
                            memberRecharge.getAmount().add(memberRecharge.getGiftAmount()));
                    
                    // 如果找到对应套餐，则更新会员有效期
                    if (rechargePackage != null && rechargePackage.getValidDays() > 0) {
                        extendMemberValidity(memberRecharge.getMemberId(), rechargePackage.getValidDays());
                    }
                }
            }
            
            return ServerResponseEntity.success(result);
        } catch (Exception e) {
            log.error("处理支付通知失败", e);
            return ServerResponseEntity.fail("处理支付通知失败: " + e.getMessage());
        }
    }

    @Override
    public ServerResponseEntity<List<MemberRecharge>> getRechargeRecords(Long memberId) {
        try {
            // 查询会员充值记录
            List<MemberRecharge> memberRecharges = memberRechargeMapper.selectByMemberId(memberId);
            return ServerResponseEntity.success(memberRecharges);
        } catch (Exception e) {
            log.error("查询充值记录失败", e);
            return ServerResponseEntity.fail("查询充值记录失败: " + e.getMessage());
        }
    }

    @Override
    public ServerResponseEntity<MemberRecharge> getRechargeDetail(String orderNo) {
        try {
            // 查询充值订单详情
            MemberRecharge memberRecharge = memberRechargeMapper.selectByOrderNo(orderNo);
            if (memberRecharge == null) {
                return ServerResponseEntity.fail("充值订单不存在");
            }
            return ServerResponseEntity.success(memberRecharge);
        } catch (Exception e) {
            log.error("查询充值订单详情失败", e);
            return ServerResponseEntity.fail("查询充值订单详情失败: " + e.getMessage());
        }
    }
    
    @Override
    public ServerResponseEntity<String> getOrderStatus(String orderNo) {
        try {
            MemberRecharge memberRecharge = memberRechargeMapper.selectByOrderNo(orderNo);
            if (memberRecharge == null) {
                return ServerResponseEntity.fail("充值订单不存在");
            }
            return ServerResponseEntity.success(memberRecharge.getStatus());
        } catch (Exception e) {
            log.error("查询订单状态失败", e);
            return ServerResponseEntity.fail("查询订单状态失败: " + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ServerResponseEntity<Boolean> cancelRechargeOrder(Long memberId, String orderNo) {
        try {
            // 查询充值订单
            MemberRecharge memberRecharge = memberRechargeMapper.selectByOrderNo(orderNo);
            if (memberRecharge == null) {
                return ServerResponseEntity.fail("充值订单不存在");
            }
            
            // 验证会员ID
            if (!memberRecharge.getMemberId().equals(memberId)) {
                return ServerResponseEntity.fail("无权操作此订单");
            }
            
            // 验证订单状态
            if (!PayConstant.OrderStatus.WAIT_PAY.equals(memberRecharge.getStatus())) {
                return ServerResponseEntity.fail("订单状态不允许取消");
            }
            
            // 更新订单状态为已关闭
            memberRecharge.setStatus(PayConstant.OrderStatus.CLOSED);
            memberRecharge.setUpdateBy(memberId.toString());
            memberRechargeMapper.updateByOrderNo(memberRecharge);
            
            // 关闭支付订单
            PayService payService = getPayService(memberRecharge.getPayType());
            boolean result = payService.closeOrder(orderNo);
            
            return ServerResponseEntity.success(result);
        } catch (Exception e) {
            log.error("取消充值订单失败", e);
            return ServerResponseEntity.fail("取消充值订单失败: " + e.getMessage());
        }
    }
    
    /**
     * 根据支付类型获取支付服务
     */
    private PayService getPayService(String payType) {
        if (PayConstant.PayType.WECHAT.equals(payType)) {
            return wechatPayService;
        } else if (PayConstant.PayType.ALIPAY.equals(payType)) {
            return alipayService;
        } else {
            throw new IllegalArgumentException("不支持的支付类型: " + payType);
        }
    }
    
    /**
     * 生成订单号
     */
    private String generateOrderNo() {
        return "RC" + System.currentTimeMillis() + UUID.randomUUID().toString().substring(0, 6);
    }
    
    /**
     * 计算赠送金额
     */
    private java.math.BigDecimal calculateGiftAmount(java.math.BigDecimal amount) {
        // 例如：充值满100送10，满500送100
        if (amount.compareTo(new java.math.BigDecimal("500")) >= 0) {
            return new java.math.BigDecimal("100");
        } else if (amount.compareTo(new java.math.BigDecimal("100")) >= 0) {
            return new java.math.BigDecimal("10");
        }
        return java.math.BigDecimal.ZERO;
    }
    
    /**
     * 根据充值金额查找对应的套餐
     */
    private RechargePackage getRechargePackageByAmount(java.math.BigDecimal amount) {
        List<RechargePackage> packages = rechargePackageMapper.selectEnabled();
        for (RechargePackage pkg : packages) {
            if (pkg.getAmount().compareTo(amount) == 0) {
                return pkg;
            }
        }
        return null;
    }
    
    /**
     * 更新会员余额
     */
    private void updateMemberBalance(Long memberId, java.math.BigDecimal amount) {
        log.info("调用会员服务更新会员 {} 余额，增加 {}", memberId, amount);
        // 调用会员服务更新余额
        ServerResponseEntity<Boolean> response = memberFeignClient.updateBalance(memberId, amount);
        if (!response.isSuccess()) {
            log.error("更新会员余额失败: {}", response.getMessage());
            throw new RuntimeException("更新会员余额失败: " + response.getMessage());
        }
    }
    
    /**
     * 延长会员有效期
     */
    private void extendMemberValidity(Long memberId, Integer days) {
        log.info("调用会员服务延长会员 {} 有效期 {} 天", memberId, days);
        // 调用会员服务延长有效期
        ServerResponseEntity<Boolean> response = memberFeignClient.extendValidity(memberId, days);
        if (!response.isSuccess()) {
            log.error("延长会员有效期失败: {}", response.getMessage());
            // 余额已更新，这里不抛异常，只记录日志
            log.error("延长会员有效期失败: " + response.getMessage());
        }
    }
} 